<template>
  <div class="img-list">
    <div v-for="(item,key) in fileList" :key="key" class="img-li-box">
      <div class="img-li-b--url" :class="{ 'bggray':item.percentage != 0 && item.percentage!= 100}">
        <img
          v-show="item.status!=='fail'"
          class="img-li-b--url-img"
          :class="{ 'noPic': getFileAttrIsPic(item.name)}"
          :src="showPicPreview(item.url,item.name,item.status)"
        />
      </div>
      <div class="img-li-b--bottom">
        <div class="img-li-b--name" :title="item.name">{{ item.name }}</div>
      </div>
      <!-- 下载 删除icon -->
      <div class="img-li-b--delete">
        <img
          v-if="item.percentage == 100 && decideFileAttrCanPreview(item.name)"
          src="./downloads.png"
          alt="下载文件"
          class="downloadImg"
          @click="handleFiledownload(item,key)"
        />
        <img
          v-if="item.percentage == 100 && decideFileAttrCanPreview(item.name)"
          src="./preview.png"
          alt="预览图片和PDF文件"
          class="previewImg"
          @click="handleFilePreview(item,key)"
        />
        <img
          v-if="item.percentage == 100 && !decideFileAttrCanPreview(item.name)"
          src="./download.png"
          alt="下载文件"
          class="downloadImgOnly"
          @click="handleFiledownload(item,key)"
        />
        <i v-if="editable != 0" class="el-icon-error removeButton" @click="handleFileRemove(item,key)" />
      </div>
      <div v-if="item.percentage != 0 && item.percentage!= 100 && item.status != 'fail'" class="img-progress-container">
        <el-progress
          type="circle"
          :width="70"
          :show-text="true"
          color="#ceab70"
          :stroke-width="15"
          :percentage="item.percentage"
          :status="proStatus(item.status)"
        />
      </div>
      <div v-if="item.status == 'fail'" class="img-progress-container">
        <img src="./723.png" alt="上传失败" class="fileImg" />
      </div>
    </div>
    <!-- 上传进度 -->
    <!-- <div v-if="!pass && progress !== 0" class="img-li-box img-li-b--progress">
                <el-progress type="circle" :percentage="progress" :status="proStatus"></el-progress>
    </div>-->
    <!-- 上传按钮 -->
    <div v-if="editable != 0" class="img-li-b--upload">
      <!-- action是指上传文件的地址，任何字符串都行，应该在基层组件里写死 -->
      <el-upload
        ref="upload"
        class="img-li-b--upl--field"
        list-type="picture-card"
        :show-file-list="false"
        action="..."
        :data="data"
        :on-change="uploadOnChange"
        :on-preview="uploadOnPreview"
        :on-remove="uploadOnRemove"
        :on-success="uploadOnSuccess"
        :on-error="uploadOnError"
        :on-progress="uploadOnProgress"
        :before-upload="beforeUpload"
        :before-remove="beforeRemove"
        :on-exceed="handleExceed"
        :file-list="fileList"
        :limit="fileCountLimit"
        :disabled="editable == 0"
        :multiple="multiple"
        :http-request="httpRequest"
        :auto-upload="false"
      >
        <img src="./up.png" alt="点击上传" class="uploadImg" />
      </el-upload>
    </div>
    <!-- 放大弹窗 -->
    <el-dialog title :visible.sync="isEnlargeImage" :modal-append-to-body="false" top="8%" width="60%">
      <img style="width:100%;" :src="enlargeImage" @click="isEnlargeImage = false" />
    </el-dialog>
  </div>
</template>

<script>
import axios from 'axios'
import {
  baseUrl,
  getUuid,
  getPercent,
  removefile,
  downloadFile
} from '@/components/Supload/uploadApi.js'
export default {
  name: 'UploadList',
  props: {
    multiple: {
      type: Boolean,
      default: true
    },
    typeLimit: {
      type: Array,
      default: () => {
        return []
      }
    },
    sizeLimit: {
      type: Object,
      default: () => {
        return {}
      }
    },
    fileList: {
      type: Array,
      default: () => {
        return []
      }
    },
    fileCountLimit: {
      type: Number,
      default: 0
    },
    data: {
      type: Object,
      default: () => {
        return {}
      }
    },
    editable: {
      type: [Number, String],
      default: 1
    }
  },
  data() {
    return {
      // 文件上传地址
      uploadUrl: '',
      // 进度条对象
      progress: 0,
      isEnlargeImage: false, // 放大图片
      enlargeImage: '', // 放大图片地址
      pass: false
    }
  },
  computed: {},
  methods: {
    proStatus(progress) {
      // 上传状态
      if (progress == 'success') {
        return 'success'
      } else if (progress == 'fail') {
        return 'exception'
      } else {
        return 'text'
      }
    },
    getFileAttrIsPic(name) {
      const last_len = name.lastIndexOf('.')
      const len = name.length
      const attr = name.substring(last_len, len)
      switch (attr) {
        case '.png':
        case '.jpg':
        case '.bmp':
        case '.jpeg':
        case '.gif':
          return false
        default:
          return true
      }
    },
    // 判断 后缀 是图片 和PDF的时候可以预览
    decideFileAttrCanPreview(name) {
      const last_len = name.lastIndexOf('.')
      const len = name.length
      const attr = name.substring(last_len, len)
      switch (attr) {
        case '.pdf':
        case '.png':
        case '.jpg':
        case '.bmp':
        case '.jpeg':
        case '.gif':
          return true
        default:
          return false
      }
    },
    showPicPreview(url, name, status) {
      const last_len = name.lastIndexOf('.')
      const len = name.length
      const attr = name.substring(last_len, len)
      if (status === 'fail') {
        return require('/')
      } else {
        switch (attr) {
          case '.png':
          case '.jpg':
          case '.bmp':
          case '.jpeg':
          case '.gif':
            return url || require('./fileImg.png')
          case '.doc':
          case '.docx':
            return require('./word.png')
          case '.xls':
          case '.xlsx':
          case '.csv':
            return require('./excel.png')
          case '.pdf':
            return require('./pdf.png')
          default:
            return require('./file.png')
        }
      }
    },
    uploadOnProgress(event, file, filelist) {
      // 开始上传
      this.$emit('uploadProgress', event, file, filelist)
    },
    uploadOnPreview(file) {
      this.$emit('previewFile', file)
    },
    uploadOnRemove(file, filelist) {
      this.$emit('removeFile', file, filelist)
    },
    // 上传文件前的钩子，用于文件的校验
    uploadOnChange(file, filelist) {
      // 判断文件大小和类型
      if (this.checkFileSize(file)) {
        if (file.status == 'ready') {
          this.pass = null
          this.progress = 0
        }
        this.$emit('changeFile', filelist)
        this.$refs['upload'].submit()
      } else {
        filelist.splice(filelist.indexOf(file), 1)
      }
    },
    // 校验文件类型
    checkFileType(fileName) {
      const type = fileName.substring(
        fileName.lastIndexOf('.'),
        fileName.length
      )
      let res = true
      const { typeLimit } = this
      if (typeLimit.length > 0) {
        typeLimit.indexOf(type) === -1 ? (res = false) : ''
      }
      if (!res) {
        this.$notify({
          title: '警告',
          message: '上传文件类型不支持',
          type: 'warning',
          duration: '3000'
        })
      }
      return res
    },
    // 校验文件大小
    checkFileSize(file) {
      let res = false
      const { sizeLimit } = this
      if (this.checkFileType(file.name)) {
        if (sizeLimit.size !== undefined) {
          let limit = ''
          switch (sizeLimit.type) {
            case 'MB':
              limit = sizeLimit.size * Math.pow(1024, 2)
              break
            case 'KB':
              limit = sizeLimit.size
              break
          }
          if (file.size > limit) {
            this.$notify({
              title: '警告',
              message: `文件大小不能大于${sizeLimit.size}${sizeLimit.type}`,
              type: 'warning',
              duration: '3000'
            })
          } else {
            res = true
          }
        } else {
          res = true
        }
      }
      return res
    },
    uploadOnSuccess(e, file) {
      // 上传附件
      this.pass = true
      this.$emit('successUpload', e, file)
    },
    uploadOnError(e, file) {
      this.$emit('errorUpload', e, file)
      this.pass = false
    },
    // 自己写的文件上传
    httpRequest(params) {
      this.getUUID(uuid => {
        const formData = new FormData()
        formData.append('file', params.file)
        axios
          .post(this.uploadUrl, formData, {
            headers: {
              'Content-Type': 'multipart/form-data'
            }
          })
          .then(res => {
            const fileid = res.data
            if (fileid) {
              this.fileList.forEach(i => {
                if (i.uid === params.file.uid) {
                  i.fileUrl = fileid
                }
              })
            }
          })
          .catch(() => {
            this.$notify.error({
              title: '错误',
              message: '文件' + params.file.name + '上传失败',
              duration: '3000'
            })
            this.fileList.forEach(i => {
              if (i.uid === params.file.uid) {
                i.status = 'fail'
                i.percentage = 0
              }
            })
            clearInterval(percentTimer)
          })
        // process 进度条的定时器
        const percentTimer = setInterval(() => {
          this.getfilePercentage(uuid, percentTimer, params.file)
        }, 500)
      })
    },
    // 获取UUID，文件上传的第一步
    getUUID(callback) {
      axios
        .get(baseUrl + getUuid)
        .then(res => {
          if (res.data.code != '0') {
            this.$notify.error({
              title: '错误',
              message: '获取UUID失败',
              duration: '3000'
            })
            return
          }
          const data = res.data.data
          this.uploadUrl = baseUrl + '/fs/file/upload?flag=' + data
          callback(data)
        })
        .catch(() => {
          this.$notify.error({
            title: '错误',
            message: '获取文件uuid失败',
            duration: '3000'
          })
        })
    },

    getfilePercentage(id, timer, thisfile) {
      axios
        .get(baseUrl + getPercent, {
          params: {
            id: id
          }
        })
        .then(res => {
          if (res.data.code != '0') {
            this.$notify.error({
              title: '错误',
              message: '获取文件百分比失败',
              duration: '3000'
            })
            clearInterval(timer)
          } else {
            const data = res.data.data
            this.fileList.forEach(i => {
              if (i.uid === thisfile.uid) {
                if (data == null) {
                  i.percentage = 0.1
                } else {
                  i.status = 'text'
                  i.percentage = parseFloat(data)
                  if (data == '100') {
                    i.status = 'success'
                    console.log(this.fileList)
                    clearInterval(timer)
                    this.$notify.success({
                      title: '成功',
                      message: '上传成功',
                      duration: '3000'
                    })
                    this.$emit('afterSuccessUpload', this.fileList)
                  }
                }
              }
            })
          }
        })
        .catch(() => {
          clearInterval(timer)
        })
    },
    beforeUpload(file) {
      this.$emit('beforeUpload', file)
    },
    beforeRemove(file, fileList) {
      this.$emit('beforeRemove', file, fileList)
    },
    handleExceed(files, fileList) {
      this.$emit('exceedFileLimit', files, fileList)
      // this.$message.warning(`当前限制选择 3 个文件，本次选择了 ${files.length} 个文件，共选择了 ${files.length + fileList.length} 个文件`);
    },
    handleFileEnlarge(_url) {
      // 放大图片
      if (_url) {
        this.enlargeImage = _url
        this.isEnlargeImage = !this.isEnlargeImage
      }
    },
    handleFiledownload(file, i) {
      if (!file.fileUrl) {
        this.$notify({
          title: '失败',
          message: '下载失败',
          type: 'error',
          duration: '3000'
        })
        return false
      }
      window.location.href = baseUrl + downloadFile + file.fileUrl.trim()
    },
    handleFilePreview(file, i) {
      if (!file.fileUrl) {
        this.$notify({
          title: '失败',
          message: '预览失败',
          type: 'error',
          duration: '3000'
        })
        return false
      }
      const last_len = file.name.lastIndexOf('.')
      const len = file.name.length
      const attr = file.name.substring(last_len, len)
      // 开新窗口
      var newwin = window.open()
      var url = baseUrl + downloadFile + file.fileUrl.trim()
      if (attr === '.pdf') {
        newwin.document.write('<embed :src="' + url + '" type="application/pdf" width="100%" height="100%">')
      } else {
        newwin.document.write('<div style="background:#f5f5f5;display:flex;justify-content:center;align-items:center;width；100%;height:100%"><img  src=' + url + ' /></div>')
      }
    },
    handleFileRemove(file, i) {
      // 删除图片
      const that = this
      that
        .$confirm('是否删除此文件？', '删除', {
          confirmButtonText: '确认',
          cancelButtonText: '取消',
          confirmButtonClass: 'el-button--primary',
          cancelButtonClass: 'el-button--primary is-plain',
          showClose: true,
          customClass: 'confirm-dialog confirm-dialog-delate'
        })
        .then(() => {
          if (file.fileUrl) {
            axios
              .post(baseUrl + removefile, {
                id: file.fileUrl.trim()
              })
              .then(function(res) {
                if (res.data.code != '0') {
                  that.$notify.error({
                    title: '错误',
                    message: '删除失败',
                    duration: '3000'
                  })
                } else {
                  that.$notify({
                    title: '成功',
                    message: '删除成功',
                    type: 'success',
                    duration: '3000'
                  })
                  // that.fileList.splice(i, 1)
                  that.$emit('removeList', i)
                }
              })
          } else {
            // that.fileList.splice(i, 1)
            that.$emit('removeList', i)
          }
        })
        .catch(meg => console.log(meg))
    }
  }
}
</script>

<style lang="scss">
@import './index.scss';
</style>
